import { format, addDays, subDays, subHours, startOfHour, getUnixTime } from 'date-fns';

// === Date Formatting ===
export function formatDate(date: Date): string {
  return format(date, 'yyyy-MM-dd HH:mm:ss');
}

export function formatDateOnly(date: Date): string {
  return format(date, 'yyyy-MM-dd');
}

export function formatTimeOnly(date: Date): string {
  return format(date, 'HH:mm:ss');
}

// === Date Calculations ===
export function getStartOfHour(date: Date = new Date()): Date {
  return startOfHour(date);
}

export function getLastHour(date: Date = new Date()): Date {
  return subHours(date, 1);
}

export function getLastHourStart(date: Date = new Date()): Date {
  return startOfHour(subHours(date, 1));
}

export function getLastDay(date: Date = new Date()): Date {
  return subDays(date, 1);
}

export function getLastNDays(n: number, date: Date = new Date()): Date {
  return subDays(date, n);
}

export function addNDays(n: number, date: Date = new Date()): Date {
  return addDays(date, n);
}

// === Date Range ===
export interface DateRange {
  start: Date;
  end: Date;
}

export function createDateRange(startDate: Date, endDate: Date): DateRange {
  if (endDate < startDate) {
    throw new Error('End date cannot be before start date');
  }
  return { start: startDate, end: endDate };
}

// === Timestamp Helpers ===
export function getTimestamp(date: Date = new Date()): number {
  return getUnixTime(date);
}

export function isValidDate(date: string | number | Date): boolean {
  const d = new Date(date);
  return d instanceof Date && !isNaN(d.getTime());
}

// === Date Comparisons ===
export function isInRange(date: Date, range: DateRange): boolean {
  return date >= range.start && date <= range.end;
}

export function getDaysDifference(startDate: Date, endDate: Date): number {
  const diffInMs = endDate.getTime() - startDate.getTime();
  return Math.ceil(diffInMs / (1000 * 60 * 60 * 24));
}

// === Common Time Ranges ===
export const timeRanges = {
  lastHour: (): DateRange => ({
    start: getLastHourStart(),
    end: new Date()
  }),
  
  last24Hours: (): DateRange => ({
    start: subHours(new Date(), 24),
    end: new Date()
  }),
  
  last7Days: (): DateRange => ({
    start: getLastNDays(7),
    end: new Date()
  }),
  
  last30Days: (): DateRange => ({
    start: getLastNDays(30),
    end: new Date()
  }),
  
  custom: (days: number): DateRange => ({
    start: getLastNDays(days),
    end: new Date()
  })
};
